home *** CD-ROM | disk | FTP | other *** search
- /********************************************/
- /* Copyright 1997 MetaCard Corporation */
- /* This source code may be used as a */
- /* template for building external */
- /* processes for use with Rev or MC. */
- /* All Other Rights Reserved */
- /********************************************/
- /*
- MetaCard template for external commands and functions
- */
- #include <stdlib.h>
- #include <stdio.h>
- #include <string.h>
- #include <math.h>
- #ifdef X11
- #include <sys/time.h>
- #include <values.h>
-
- #ifdef SELECT
- #ifndef LINUX
- /* some systems don't have select.h and/or stream.h. If yours doesn't
- delete the offending #include */
- #include <sys/select.h>
- #include <sys/stream.h>
- #endif
- #else
- #include <poll.h>
- #endif
- #include <X11/Xlib.h>
- #elif defined WIN32
- #include <time.h>
- #include <windows.h>
- #elif defined MACOS
- #include <Quickdraw.h>
- #include <QDOffscreen.h>
- #endif
- #include "XCmdGlue.h"
- #include "external.h"
-
- /*
- * This global table has one entry per XCMD/XFCN.
- * The first entry is the name of the handler
- * The second entry is the type (XCOMMAND or XFUNCTION)
- * The third entry is a space for the atom (used by MetaCard)
- * The fourth entry is the name of the 'C' function to call
- * The fifth entry is a callback called if the user aborts
- * Note that the last entry in the table is a NULL entry
- * which is used to measure the size of the table.
- */
-
- Xternal Xtable[] = {
- {"xgetvar", XFUNCTION, 0, XGetVar, XCabort},
- {"xsetvar", XCOMMAND, 0, XSetVar, XCabort},
- {"xsetarray", XCOMMAND, 0, XSetArray, XCabort},
- {"xgetarray", XFUNCTION, 0, XGetArray, XCabort},
- {"convolve", XCOMMAND, 0, XConvolve, XCabort},
- {"sprintf", XCOMMAND, 0, XCsprintf, XCabort},
- {"xatan2", XFUNCTION, 0, XFatan2, XCabort},
- {"callbacktests", XCOMMAND, 0, XCcallbacktests, XCabort},
- {"life_init", XFUNCTION, 0, XFlife_init, XCabort},
- {"life_create", XCOMMAND, 0, XClife_create, XCabort},
- {"life_delay", XCOMMAND, 0, XClife_delay, XCabort},
- {"life_cease", XCOMMAND, 0, XClife_cease, XCabort},
- {"", XNONE, 0, NULL, NULL}
- };
-
- /*
- * This string identifies this external to the engine
- */
- char Xname[] = "Template Xternals";
-
- /*
- * local variables
- */
- #define GRID_SIZE 40
- #define CELL_SIZE 8
- static char g1[GRID_SIZE + 2][GRID_SIZE + 2];
- static char g2[GRID_SIZE + 2][GRID_SIZE + 2];
- static char (*oldgrid)[GRID_SIZE + 2];
- static char (*newgrid)[GRID_SIZE + 2];
- #if defined X11
- static GC gc;
- static Pixmap pm;
- static unsigned long livecolor;
- static unsigned long deadcolor;
- #elif defined WIN32
- static HBITMAP bm;
- static HBITMAP oldbitmap;
- static HDC memhdc;
- static HBRUSH livebrush; //handle to red color brush
- static HBRUSH deadbrush; //handle to gray color brush
- static HBRUSH oldbrush; //old brush
- #elif defined MACOS
- static GWorldPtr gw;
- static RGBColor livecolor;
- static RGBColor deadcolor;
- static Rect rect;
- static CGrafPtr oldport;
- static GDHandle olddevice;
- #endif
-
-
- #ifdef __STDC__
- void XGetVar(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XGetVar(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- int retvalue;
- char *key = NULL;
- char *retstr = NULL;
- *pass = False;
- *error = False;
- if (nargs == 2){
- MCstring val = {NULL,0};
- key = args[1];
- GetVariableEx(args[0],key,&val,&retvalue);
- if (val.sptr != NULL){
- retstr = malloc(val.length+1);
- retstr[val.length] = '\0';
- memcpy(retstr,val.sptr,val.length);
- }
- }
- if (retstr == NULL)
- retstr = calloc(1, 1);
- *retstring = retstr;
- }
-
- #ifdef __STDC__
- void XSetVar(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XSetVar(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- int retvalue;
- char *key = NULL;
- char *retstr = NULL;
- *pass = False;
- *error = False;
- if (nargs == 3){
- MCstring tval;
- tval.sptr = args[2];
- tval.length = strlen(args[2]);
- key = args[1];
- SetVariableEx(args[0],key,&tval,&retvalue);
- }
- if (retstr == NULL)
- retstr = calloc(1, 1);
- *retstring = retstr;
- }
-
- #ifdef __STDC__
- void XSetArray(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XSetArray(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- int retvalue;
- char *retstr = NULL;
- char **keys = NULL;
- int nelements = 0;
- *pass = False;
- *error = False;
- if (nargs >= 2)
- {
- char *tptr = args[1];
- char *lastptr = NULL;
- char *keyptr = NULL;
- MCstring *tstrings;
- Bool usekeys = False;
- int count = 1;
- if (nargs == 3 && (strncmp(args[2],"TRUE",4) == 0))
- usekeys = True;
- do{
- if (*tptr == '\n')
- count++;
- }while(*++tptr);
- if (usekeys){
- keys = (char **)malloc(sizeof(char *)*count);
- memset(keys,0,sizeof(char *)*count);
- }
- tstrings = (MCstring *)malloc(sizeof(MCstring)*count);
- tptr = args[1];
- lastptr = tptr;
- while (1){
- if (*tptr == '\n' || *tptr == '\0'){
- if (usekeys == True){
- keyptr = lastptr;
- while(++keyptr < tptr){
- if (*keyptr == ','){
- *keyptr = '\0';
- keys[nelements] = lastptr;
- lastptr = keyptr+1;
- break;
- }
- }
- }
- tstrings[nelements].sptr = lastptr;
- tstrings[nelements].length = tptr - lastptr;
- lastptr = tptr+1;
- nelements++;
- if (*tptr == '\0')
- break;
- }
- tptr++;
- }
- SetArray(args[0],nelements,tstrings,keys,&retvalue);
- free(tstrings);
- if (usekeys == True)
- free(keys);
- }
- if (retstr == NULL)
- retstr = calloc(1, 1);
- *retstring = retstr;
- }
-
- #ifdef __STDC__
- void XGetArray(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XGetArray(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- int retvalue;
- char *retstr = NULL;
- MCstring *values = NULL;
- char **keys = NULL;
- int nelements = 0;
- char *tptr = NULL;
- int size = 0;
- int i;
- *pass = False;
- *error = False;
- GetArray(args[0],&nelements,values,keys,&retvalue);
- if (nelements != 0){
- values = malloc(sizeof(MCstring) * nelements);
- keys = malloc(sizeof(char *) * nelements);
- GetArray(args[0],&nelements,values,keys,&retvalue);
- for (i = 0; i < nelements; i++){
- MCstring *s = &values[i];
- char *key = keys[i];
- int klength = strlen(key);
- tptr = realloc(tptr, size + s->length + 1 + klength + 1);
- memcpy(&tptr[size],key,klength);
- size += klength;
- tptr[size++] = '\t';
- memcpy(&tptr[size],s->sptr,s->length);
- size += s->length;
- tptr[size++] = '\n';
- }
- tptr[--size] = '\0';
- retstr = tptr;
- free(values);
- free(keys);
- }
- if (retstr == NULL)
- retstr = calloc(1, 1);
- *retstring = retstr;
- }
-
- #define RGBAtoFOUR(r, g, b, a) ((int)(((a) << 24) | ((r) << 16)\
- | ((g) << 8) | (b)))
- #define FOURtoB(rgb) ((rgb) & 0xff)
- #define FOURtoG(rgb) (((rgb) >> 8) & 0xff)
- #define FOURtoR(rgb) (((rgb) >> 16) & 0xff)
- #define FOURtoA(rgb) ((rgb) >> 24)
-
- #ifdef __STDC__
- int get255(int n)
- #else
- int get255(n)
- int n;
- #endif
- {
- if (n > 254) return 255;
- if (n < 0) return 0;
- return n;
- }
-
-
- #ifdef __STDC__
- void XConvolve(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XConvolve(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- int retvalue;
- *pass = False;
- *error = False;
- if (nargs == 6){
- MCstring image;
- char emp[] = "";
- GetVariableEx(args[0],emp,&image,&retvalue); //get image
- if (image.sptr != NULL){
- MCstring matrixelement;
- char *convimage;
- int convmatrix[3][3];
- int width,height, bytesperline, scale,i,j;
- char keybuffer[8];
- Bool success = True;
- width = atoi(args[1]); //argument 2 contains width of image
- height = atoi(args[2]); //argument 3 contains height of image
- scale = atoi(args[3]); //get scale for convolution operation
- bytesperline = image.length/height; //need this info for convolution filter
- convimage = malloc(image.length); //allocate space for convoluted image (same size as original)
- for (i = 0; i < 3; i++){ //populate matrix with elements from MC array
- for (j = 0; j < 3; j++) {
- sprintf(keybuffer ,"%d,%d", i+1, j+1); //create key (our MC array starts at 1)
- GetVariableEx(args[4], keybuffer, &matrixelement,&retvalue); //get element from array
- if (matrixelement.sptr == NULL) { //if not found throw an error
- *retstring = istrdup("element not found in matrix");
- success = False;
- break;
- }
- else
- convmatrix[i][j] = atoi(matrixelement.sptr);
- }
- }
- if (success == True) {
- MCstring newimage;
- int x,y;
- for (y = 1; y < height-2; y++) {
- int *O = (int *)&convimage[y * bytesperline];
- int *T = (int *)&image.sptr[(y-1) * bytesperline];
- int *C = (int *)&image.sptr[(y) * bytesperline];
- int *B = (int *)&image.sptr[(y+1) * bytesperline];
- for (x = 1; x < width - 2;x++) {
- int red = get255 ((
- (FOURtoR(T[x-1])*convmatrix[0][0]) + (FOURtoR(T[x])*convmatrix[0][1]) + (FOURtoR(T[x+1])*convmatrix[0][2])
- + (FOURtoR(C[x-1])*convmatrix[1][0]) + (FOURtoR(C[x])*convmatrix[1][1]) + (FOURtoR(C[x+1])*convmatrix[1][2])
- + (FOURtoR(B[x-1])*convmatrix[2][0]) + (FOURtoR(B[x])*convmatrix[2][1]) + (FOURtoR(B[x+1])*convmatrix[2][2]))/scale);
- int green = get255 ((
- (FOURtoG(T[x-1])*convmatrix[0][0]) + (FOURtoG(T[x])*convmatrix[0][1]) + (FOURtoG(T[x+1])*convmatrix[0][2])
- + (FOURtoG(C[x-1])*convmatrix[1][0]) + (FOURtoG(C[x])*convmatrix[1][1]) + (FOURtoG(C[x+1])*convmatrix[1][2])
- + (FOURtoG(B[x-1])*convmatrix[2][0]) + (FOURtoG(B[x])*convmatrix[2][1]) + (FOURtoG(B[x+1])*convmatrix[2][2]))/scale);
- int blue = get255 ((
- (FOURtoB(T[x-1])*convmatrix[0][0]) + (FOURtoB(T[x])*convmatrix[0][1]) + (FOURtoB(T[x+1])*convmatrix[0][2])
- + (FOURtoB(C[x-1])*convmatrix[1][0]) + (FOURtoB(C[x])*convmatrix[1][1]) + (FOURtoB(C[x+1])*convmatrix[1][2])
- + (FOURtoB(B[x-1])*convmatrix[2][0]) + (FOURtoB(B[x])*convmatrix[2][1]) + (FOURtoB(B[x+1])*convmatrix[2][2]))/scale);
- O[x] = RGBAtoFOUR(red,green,blue,0x00);
- }
- }
- newimage.sptr = convimage;
- newimage.length = image.length;
- SetVariableEx(args[5],"",&newimage,&retvalue); //set value of variable to resulting image
- *retstring = calloc(1, 1);
- }
- free(convimage);
- }
- }
- else
- *retstring = istrdup("must pass 6 arguments");
- }
-
- /*
- * Call the c library sprintf with a format and argument string.
- * A more complete routine would include checks on the the validity
- * of the arguments and allow more than one argument to be passed.
- * This routine should actually be an XFCN, since it returns a value.
- */
- #ifdef __STDC__
- void XCsprintf(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XCsprintf(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- fprintf(stderr, "XCsprintf called with nargs %d, arg1 is %s\n",
- nargs, args[0]);
- *pass = False;
- if (nargs != 2) {
- /* only set error to true when a syntax error occurs, as it
- causes the script to stop execution at this point */
- *error = True;
- *retstring = istrdup("printf: must pass 2 arguments");
- }
- else {
- *error = False;
- *retstring = malloc(strlen(args[0]) + strlen(args[1]) + 1);
- sprintf(*retstring, args[0], args[1]);
- }
- }
-
- /*
- * Call the c library atan2 with the required two arguments.
- * A more complete routine would include setting up a matherr
- * routine and checking errno for DOMAIN errors.
- */
- #ifdef __STDC__
- void XFatan2(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XFatan2(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- fprintf(stderr, "XCatan2 called with nargs %d, arg1 is %s\n",
- nargs, args[0]);
- *pass = False;
- if (nargs != 2) {
- /* only set error to true when a syntax error occurs, as it
- causes the script to stop execution at this point */
- *error = True;
- *retstring = istrdup("atan2: must pass 2 arguments");
- }
- else {
- *error = False;
- *retstring = malloc(16);
- sprintf(*retstring, "%G", atan2(atof(args[0]), atof(args[1])));
- }
- }
-
- /*
- * Call back into MetaCard and get or set the contents of the
- * objects specified in the argument list.
- */
- #ifdef __STDC__
- void XCcallbacktests(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XCcallbacktests(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- int retvalue;
- char buffer[256];
- char *mcstring;
- #ifdef MACOS
- unsigned long seconds;
- #endif
-
- /* activate a card script handler */
- sprintf(buffer, "doSomething %s", args[0]);
- SendCardMessage(buffer, &retvalue);
-
- /* tell the engine to execute a command */
- #ifndef MACOS
- sprintf(buffer, "put \"Message time %d\" into field %s",
- (int)time(NULL), args[1]);
- #else //MAC platform
- GetDateTime(&seconds);
- sprintf(buffer, "put \"Message time %d\" into field %s",
- (int)seconds, args[1]);
- #endif
- SendMCMessage(buffer, &retvalue);
-
- /* get a global, tell MC to add 1 to the result, then set the global */
- mcstring = GetGlobal(args[2], &retvalue);
- sprintf(buffer, "%s + 1", mcstring);
- free(mcstring);
- mcstring = EvalExpr(buffer, &retvalue);
- SetGlobal(args[2], mcstring, &retvalue);
- free(mcstring);
-
- /* The first parameter to field routines should be:
- "true" to look for the field on the card,
- "false" to look only on the background,
- "" to look on both the card and the background
- or a group name to look for the field in that group. */
-
- mcstring = GetFieldByName("", args[3], &retvalue);
- SetFieldByName("", args[6], mcstring, &retvalue);
- free(mcstring);
-
- mcstring = GetFieldByNum("", atoi(args[4]), &retvalue);
- SetFieldByNum("", atoi(args[7]), mcstring, &retvalue);
- free(mcstring);
-
- mcstring = GetFieldById("", atoi(args[5]), &retvalue);
- SetFieldById("", atoi(args[8]), mcstring, &retvalue);
- free(mcstring);
-
- /* get an expression from a local variable, evaluate the expression
- in the local context, and put the value back into the local variable */
- mcstring = GetVariable(args[9], &retvalue);
- strcpy(buffer, mcstring);
- free(mcstring);
- mcstring = EvalExpr(buffer, &retvalue);
- SetVariable(args[9], mcstring, &retvalue);
- free(mcstring);
-
- *pass = False;
- *error = False;
- *retstring = istrdup("callbacktest done");
- }
-
- /*
- * Do one generation of the life simulation, coloring the squares
- * for each of the live cells. This function is called at on the
- * idle event, the rate of which is controlled by the X_set_idle_rate
- * function, which is called in the XClife_delay function.
- */
- void life_generation()
- {
- int retvalue;
- int x, y;
-
- #ifdef X11
- if (pm == 0)
- return;
- #elif defined WIN32
- if (bm == NULL)
- return;
- #elif defined MACOS
- if (gw == NULL)
- return;
- #endif
- if (oldgrid == g1) {
- oldgrid = g2;
- newgrid = g1;
- }
- else {
- oldgrid = g1;
- newgrid = g2;
- }
- for (x = 1 ; x <= GRID_SIZE ; x++) {
- for (y = 1 ; y <= GRID_SIZE ; y++) {
- int neighbors = oldgrid[x - 1][y - 1] + oldgrid[x][y - 1]
- + oldgrid[x + 1][y - 1] + oldgrid[x - 1][y] + oldgrid[x + 1][y]
- + oldgrid[x - 1][y + 1] + oldgrid[x][y + 1] + oldgrid[x + 1][y + 1];
- if (neighbors == 2)
- newgrid[x][y] = oldgrid[x][y];
- else {
- if (neighbors == 3)
- newgrid[x][y] = 1;
- else
- newgrid[x][y] = 0;
- #ifdef X11
- if (newgrid[x][y] != oldgrid[x][y]) {
- if (newgrid[x][y])
- XSetForeground(MCdpy, gc, livecolor);
- else
- XSetForeground(MCdpy, gc, deadcolor);
- XFillRectangle(MCdpy, pm, gc, (x - 1) * CELL_SIZE + 1,
- (y - 1) * CELL_SIZE + 1,
- CELL_SIZE - 2, CELL_SIZE - 2);
- }
- #elif defined WIN32
- SelectObject(memhdc, bm);
- if (newgrid[x][y] != oldgrid[x][y]) {
- if (newgrid[x][y]) {
- SelectObject(memhdc,livebrush);
- SelectObject(memhdc, GetStockObject(NULL_PEN));
- }
- else {
- SelectObject(memhdc, deadbrush);
- SelectObject(memhdc, GetStockObject(NULL_PEN));
- }
- Rectangle(memhdc, (x - 1) * CELL_SIZE + 1, (y - 1) * CELL_SIZE + 1,
- (x -1) * CELL_SIZE + 1 + (CELL_SIZE - 2),
- (y - 1) * CELL_SIZE + 1 + (CELL_SIZE - 2));
- }
- SelectObject(memhdc, oldbrush);
- SelectObject(memhdc, oldbitmap);
- #elif defined MACOS
- GetGWorld(&oldport, &olddevice);
- SetGWorld(gw, NULL);
- if (newgrid[x][y] != oldgrid[x][y]) {
- if (newgrid[x][y])
- RGBForeColor(&livecolor);
- else
- RGBForeColor(&deadcolor);
- SetRect(&rect, (x - 1) * CELL_SIZE + 1, (y - 1) * CELL_SIZE + 1,
- (x -1) * CELL_SIZE + 1 + (CELL_SIZE - 2),
- (y - 1) * CELL_SIZE + 1 + (CELL_SIZE - 2));
- PaintRect(&rect);
- SetGWorld(oldport, olddevice);
- }
- #endif
- }
- }
- }
- ShowImageByNum("", 1, &retvalue);
- }
-
- /*
- * Create pixmap and clear it, then set imagePixmapId property.
- * Get GC and colors used for drawing cells. Put some live cells
- * in at random.
- */
- #ifdef __STDC__
- void XFlife_init(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XFlife_init(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- int x, y;
- X_set_idle_handler(life_generation);
- for (x = 1 ; x <= GRID_SIZE ; x++)
- for (y = 1 ; y <= GRID_SIZE ; y++)
- if (rand() > RAND_MAX / 2)
- g1[x][y] = 1;
- *pass = False;
- *error = False;
- *retstring = malloc(16);
- #ifdef X11
- {
- XColor c;
- XWindowAttributes xwa;
- int size = GRID_SIZE * CELL_SIZE;
- XGetWindowAttributes(MCdpy, MCwin, &xwa);
- pm = XCreatePixmap(MCdpy, MCwin, size, size, xwa.depth);
- gc = DefaultGCOfScreen(xwa.screen);
- XAllocNamedColor(MCdpy, xwa.colormap, "red", &c, &c);
- livecolor = c.pixel;
- XAllocNamedColor(MCdpy, xwa.colormap, "gray", &c, &c);
- deadcolor = c.pixel;
- XSetForeground(MCdpy, gc, deadcolor);
- XFillRectangle(MCdpy, pm, gc, 0, 0, GRID_SIZE * CELL_SIZE,
- GRID_SIZE * CELL_SIZE);
- sprintf(*retstring, "%ld", pm);
- }
- #elif defined WIN32
- {
- int size = GRID_SIZE * CELL_SIZE;
- HDC winhdc = GetDC(HWND_DESKTOP);
- memhdc = CreateCompatibleDC(winhdc);
- if ((bm = CreateCompatibleBitmap(winhdc, size, size)) == NULL) //compatible to screen
- return;
- ReleaseDC(NULL, winhdc);
- livebrush = CreateSolidBrush(RGB(255, 0, 0));
- deadbrush = CreateSolidBrush(RGB(128, 128, 128)); // Create a gray brush.
- // deadbrush = CreateSolidBrush(RGB(0, 255, 0)); //green
- oldbitmap = SelectObject(memhdc, bm); //select bitmap into memory DC
- oldbrush = SelectObject(memhdc, deadbrush);
- if (!Rectangle(memhdc, 0, 0, size, size))
- return;
- SelectObject(memhdc, oldbitmap);
- SelectObject(memhdc, oldbrush);
- sprintf(*retstring, "%ld", bm);
- }
- #elif defined MACOS
- {
-
- QDErr err;
- short devdepth;
- GDHandle hgraf;
- PixMapHandle hpixmap;
- SetRect(&rect, 0, 0, GRID_SIZE * CELL_SIZE, GRID_SIZE * CELL_SIZE);
- hgraf = GetMainDevice(); //get main screen graphic device handle
- HLock((Handle)hgraf);
- hpixmap = ((GDPtr)*hgraf)->gdPMap;
- HLock((Handle)hpixmap);
- devdepth = ((PixMapPtr)*hpixmap)->pixelSize;//get main screen device depth
- HUnlock((Handle)hpixmap);
- HUnlock((Handle)hgraf);
- err = NewGWorld(&gw, devdepth, &rect, NULL, NULL, 0);
- if ((gw == NULL) || (err != noErr))
- return;
- GetGWorld(&oldport, &olddevice);
- SetGWorld(gw, NULL);
- deadcolor.red = deadcolor.green = deadcolor.blue = 32768; // = 128 color gray
- livecolor.red = 65535; // = 256 color red
- livecolor.green = livecolor.blue = 0;
- RGBForeColor(&deadcolor);
- PaintRect(&rect);
- SetGWorld(oldport, olddevice);
- sprintf(*retstring, "%ld", gw); //return the GWorld created to the calling program
- }
- #endif
- }
-
- /*
- * Set the cell at the x,y coordinate specified to the "live" state.
- */
- #ifdef __STDC__
- void XClife_create(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XClife_create(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- int x, y;
- x = atoi(args[0]) / CELL_SIZE + 1;
- y = atoi(args[1]) / CELL_SIZE + 1;
- newgrid[x][y] = 1;
-
- #if defined X11
- XSetForeground(MCdpy, gc, livecolor);
- XFillRectangle(MCdpy, pm, gc, (x - 1) * CELL_SIZE + 1,
- (y - 1) * CELL_SIZE + 1,
- CELL_SIZE - 2, CELL_SIZE - 2);
- #elif defined WIN32
- SelectObject(memhdc,livebrush);
- SelectObject(memhdc, GetStockObject(NULL_PEN));
- SelectObject (memhdc, bm);
- Rectangle(memhdc, (x - 1) * CELL_SIZE + 1, (y - 1) * CELL_SIZE + 1,
- (x - 1) * CELL_SIZE + 1 + (CELL_SIZE - 2),
- (y - 1) * CELL_SIZE + 1 + (CELL_SIZE - 2));
- SelectObject(memhdc, oldbrush);
- SelectObject(memhdc, oldbitmap);
- #elif defined MACOS
- GetGWorld(&oldport, &olddevice);
- SetGWorld(gw, NULL);
- RGBForeColor(&livecolor);
- SetRect(&rect, (x - 1) * CELL_SIZE + 1, (y - 1) * CELL_SIZE + 1,
- (x - 1) * CELL_SIZE + 1 + (CELL_SIZE - 2), (y - 1) * CELL_SIZE + 1 + (CELL_SIZE - 2));
- PaintRect(&rect);
- SetGWorld(oldport, olddevice);
- #endif
- *pass = False;
- *error = False;
- *retstring = calloc(1, 1);
- }
-
- /*
- * Set the delay between generations
- */
- #ifdef __STDC__
- void XClife_delay(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XClife_delay(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
- X_set_idle_rate(atoi(args[0]));
- *pass = False;
- *error = False;
- *retstring = calloc(1, 1);
- }
-
- /*
- * Stop life
- */
- #ifdef __STDC__
- void XClife_cease(char *args[], int nargs, char **retstring,
- Bool *pass, Bool *error)
- #else
- void XClife_cease(args, nargs, retstring, pass, error)
- char *args[];
- int nargs;
- char **retstring;
- Bool *pass;
- Bool *error;
- #endif
- {
-
- #ifdef X11
- XWindowAttributes xwa;
- XGetWindowAttributes(MCdpy, MCwin, &xwa);
- XSync(MCdpy, False); /* make sure all drawing is done */
- XFreeColors(MCdpy, xwa.colormap, &livecolor, 1, 0);
- XFreeColors(MCdpy, xwa.colormap, &deadcolor, 1, 0);
- XFreePixmap(MCdpy, pm);
- pm = 0;
- #elif defined WIN32
- DeleteObject(bm);
- bm = NULL;
- DeleteObject(livebrush);
- DeleteObject(deadbrush);
- DeleteDC(memhdc);
- #elif defined MACOS
- if (gw != NULL){
- DisposeGWorld(gw);
- gw = NULL;
- }
- #endif
- *pass = False;
- *error = False;
- *retstring = calloc(1, 1);
- }
-
- void XCabort()
- {
- fprintf(stderr, "external abort");
- }
-
- #ifdef X11
- #ifdef __STDC__
- void main(int argc, char *argv[], char *envp[])
- #else
- void main(argc, argv, envp)
- int argc;
- char *argv[];
- char *envp[];
- #endif
- {
- int retval;
- fprintf(stderr, "external startup\n");
- if (!X_init(argc, argv, envp, Xtable, Xname))
- exit(-1);
- X_main_loop();
- retval = X_close();
- fprintf(stderr, "external exit\n");
- exit(retval);
- }
- #endif
-